// 通过defineStore来创建各个小仓库
import { defineStore } from 'pinia';
// 引入封装好的token函数:分别是读取,删除,存储
import {getToken,removeToken,setToken,} from '../utils/token-utils';
import type { UserInfoState } from './interface';
// 引入element-plus的消息提示
import { ElMessage } from 'element-plus';
// 引入静态路由
import {AnyRouter,allAsyncRoutes,staticRoutes,} from '@/router/routes';
// 引入封装的请求函数
import {reqUserInfo,reqLogin,reqLogOut,} from '@/api/acl/login';
// 引入ts定义数据类型
import type { UserInfo,LoginResponseData } from '@/api/acl/types/acl';
import router from '@/router';
/**
 * 用户信息
 * @methods setUserInfos 设置用户信息
 */
// 用defineStore创建的小仓库默认被大仓库管理
export const useUserInfoStore = defineStore('userInfo', {
  // 存放数据的地方
  state: (): LoginResponseData => ({
    token: getToken() as string, //本地存储toekn
    name: '', //用户名称
    avatar: '', //头像
    menuRoutes: [],
    buttons: [],
  }),

  actions: {
    // 登录的回调
    async login(username: string, password: string) {
      // 发请求携带用户名和密码等参数
      let reslut = await reqLogin({ username, password });
      // 小仓库存储token
      this.token = reslut.token;
      // 本地存储token
      setToken(reslut.token);
      // console.log(reslut)
    },
    // 验证用户信息
    async getInfo() {
      // 发请求获取用户信息(需要携带token,在请求头中已携带)
      let reslut: UserInfo = await reqUserInfo();
      // console.log(reslut)
      // 替换请求数据的用户名称
      this.name = reslut.name;
      // 替换请求数据的用户头像
      this.avatar = reslut.avatar;
      // this.menuRoutes = staticRoutes;
      // //存储用户信息之按钮权限数组
      this.buttons = reslut.buttons;
      // 决定左侧菜单的生成 {静态路由 +  过滤完毕的动态路由+ 任意路由}
      const userShowAsyncRoute = filterAsyncRoute(allAsyncRoutes,reslut.routes);
      // 动态生成左侧菜单:相当于设置导航按钮
      this.menuRoutes = [...staticRoutes,...userShowAsyncRoute,AnyRouter];
     
      // 动态给路由器追加路由
      // 如果不书写下面代码-router.getRoutes,路由器只管理静态路由
      [...userShowAsyncRoute,AnyRouter].forEach((item)=>{
        router.addRoute(item)
      })
    },
    // 退出登录
    async reset() {
      // 发请求退出登录(需要携带token,在请求头中已携带)
      await reqLogOut();
      // 删除local中保存的token
      removeToken();
      // 提交重置用户信息的mutation
      this.token = '';
      this.name = '';
      this.avatar = '';

      // 清除全部的路由
      this.menuRoutes.forEach((item:any)=>{
        // 清楚全部的路由,根据路由的name
        router.removeRoute(item.name)
      })

      //注册静态路由
      staticRoutes.forEach((item:any)=>{
        //动态追加路由对象
        router.addRoute(item);
      })
    },
  },
});

// 过滤异步的路由
function filterAsyncRoute(allAsyncRoutes: any,ALLroutes: any) {
  // 拿所有的异步路由遍历
  return allAsyncRoutes.filter((item: any) => {
    // 看异步的路由在所有的路由对象里有没有出现过,如果有,就过滤出来,
    if (ALLroutes.includes(item.name)) {
      // 看异步路由是否有字路由,且子路由里面也有路由
      if (item.children && item.children.length > 0) {
        // 过滤出来的子路由赋值给异步路由的子路由
        item.children = filterAsyncRoute(item.children,ALLroutes);
      }
      // 返回
      return true;
    }
  });
}
